package com.begamer.card.controller;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.log4j.Logger;
import org.springframework.web.servlet.ModelAndView;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.begamer.card.cache.Cache;
import com.begamer.card.cache.PlayerInfo;
import com.begamer.card.common.util.Random;
import com.begamer.card.common.util.RequestUtil;
import com.begamer.card.common.util.Statics;
import com.begamer.card.common.util.StringUtil;
import com.begamer.card.common.util.binRead.BagCostData;
import com.begamer.card.common.util.binRead.BloodValueData;
import com.begamer.card.common.util.binRead.CardData;
import com.begamer.card.common.util.binRead.CardExpData;
import com.begamer.card.common.util.binRead.EventData;
import com.begamer.card.common.util.binRead.FBeventData;
import com.begamer.card.common.util.binRead.PlayerData;
import com.begamer.card.common.util.binRead.VipData;
import com.begamer.card.json.command2.EventBattleJson;
import com.begamer.card.json.command2.EventBattleLogJson;
import com.begamer.card.json.command2.EventBattleLogResultJson;
import com.begamer.card.json.command2.EventBattleResultJson;
import com.begamer.card.log.BattleCheckLogger;
import com.begamer.card.log.ErrorLogger;
import com.begamer.card.log.PlayerLogger;
import com.begamer.card.model.pojo.Card;
import com.begamer.card.model.pojo.CardGroup;

public class EventController extends AbstractMultiActionController
{
	private static final Logger logger=Logger.getLogger(PkController.class);
 	private static Logger playlogger =PlayerLogger.logger;
 	private static Logger errorlogger = ErrorLogger.logger;
 	private static Logger battleCheckLogger=BattleCheckLogger.logger;
 	
 	/**校验战报程度0-100**/
	private static int checkPro=100;
	public ModelAndView fBEventBattleInit(HttpServletRequest request ,HttpServletResponse response)
	{
		try{
			//检验密钥
			ModelAndView checkResult = RequestUtil.check(request);
			if(checkResult != null)
			{
				return checkResult;
			}
			//获取json
			JSONObject jsonObject = RequestUtil.getJsonObject(request);
			EventBattleJson ebj =JSONObject.toJavaObject(jsonObject, EventBattleJson.class);
			EventBattleResultJson ebrj =new EventBattleResultJson();
			if(ebj !=null)
			{
				PlayerInfo pi =Cache.getInstance().getPlayerInfo(ebj.playerId, request.getSession());
				if(pi !=null)
				{
					int id =ebj.id;//关卡id
					FBeventData fbData =FBeventData.getFBeventData(id);
					HashMap<Integer, String> fbMap1 =pi.getFBnumMap1();
					HashMap<Integer, String> fbMap2 =pi.getFBnumMap2();
					HashMap<Integer, String> fbMap =null;
					long curTime =System.currentTimeMillis();
					//校验
					int errroCode=0;
					if(fbData.timestyle==1)
					{
						fbMap =fbMap1;
					}
					else if(fbData.timestyle==2)
					{
						fbMap =fbMap2;
					}
					if(errroCode ==0)//校验等级
					{
						if(pi.player.getLevel()<fbData.unlocklevel)
						{
							errroCode =57;
						}
					}
					if(errroCode==0)
					{
						if(fbMap.containsKey(id))//校验进入次数
						{
							int entry =StringUtil.getInt(fbMap.get(id).split("-")[1]);
							if(pi.player.getVipLevel()>0)//vip玩家进入次数读vip表
							{
								VipData vData =VipData.getVipData(pi.player.getVipLevel());
								if(vData !=null && entry>=vData.activity)
								{
									errroCode =24;
								}
							}
							else//普通玩家进入次数读fbevent表
							{
								if(entry>=fbData.entry)
								{
									errroCode =24;
								}
							}
							
						}
					}
					if(errroCode ==0)//校验体力
					{
						if(pi.player.getPower()<fbData.cost)
						{
							errroCode =27;
						}
					}
					CardGroup cg=pi.getCardGroup();
					String [] s =Statics.drops(id, cg);
					if(errroCode ==0)//校验背包容量
					{
						if(s !=null && s.length>0)
						{
							if(!Statics.checkPackage(s, pi))
							{
								errroCode =53;
								BagCostData bd=BagCostData.getData(pi.player.getBuyBagTimes()+1);
								if(bd==null)
								{
									errroCode =131;
								}
							}
						}
					}
					if(errroCode ==0)
					{
						EventData eData =EventData.getEventData(ebj.eid);
						long time =0;
						if(eData !=null)
						{
							if(eData.positionid ==1)
							{
								time =pi.eventcdtime1;
							}
							else if(eData.positionid ==2)
							{
								time =pi.eventcdtime2;
							}
							else if(eData.positionid ==3)
							{
								time =pi.eventcdtime3;
							}
							if(time !=0)//校验冷却时间
							{
								if (eData.nametype == 2)
								{
									int cdtime =(int)(curTime-time)/1000;
									if(cdtime <10*60)
									{
										errroCode =86;
									}
								}
							}
						}
						else
						{
							errorlogger.info("edata is null");
						}
					}
					//功能
					if(errroCode ==0)
					{
						ebrj.id=ebj.id;
						
						ebrj.cs0=cg.getBattleData();
						ebrj.cs1=FBeventData.getMonsterData(ebj.id);
						ebrj.s =s;
						//双方合体技
						int[] us0=new int[3];
						us0[0]=cg.unitId;
						
						ebrj.us0=us0;
						ebrj.bNum =pi.bNum+1;
						int[] maxEnergys={pi.player.getMaxEnergy(),0};
						ebrj.mes=maxEnergys;
						ebrj.initE=VipData.getInitEnergy(pi.player.getVipLevel());
						ebrj.eid =ebj.eid;
						ebrj.raceAtts=Statics.getRaceAttris(pi);
						//记录战斗信息
						pi.ebrj =ebrj;
						playlogger.info("玩家"+pi.player.getId()+":副本战斗初始数据");
					}
					else
					{
						ebrj.errorCode =errroCode;
					}
				}
				else
				{
					ebrj.errorCode =-3;
				}
			}
			else
			{
				ebrj.errorCode =-1;
			}
			
			//获取参数
			Cache.recordRequestNum(ebrj);
			String msg = JSON.toJSONString(ebrj);
			logger.info("msg:"+msg);
			RequestUtil.setResponseMsg(request, msg);
			return new ModelAndView("/user/result.vm");
		}
		catch (Exception e) 
		{
			errorlogger.error(this.getClass().getName()+"->"+Thread.currentThread().getStackTrace()[1].getMethodName()+"():",e);
			RequestUtil.removeKey(request);
			String newKey = RequestUtil.setNewKey(request);
			RequestUtil.setResult(request, newKey);
		}
		return new ModelAndView("/user/result.vm");
	}
	/**副本战斗结束**/
	public ModelAndView fBEventBattleOver(HttpServletRequest request , HttpServletResponse response)
	{
		try{
			//检验密钥
			ModelAndView checkResult = RequestUtil.check(request);
			if(checkResult != null)
			{
				return checkResult;
			}
			//获取json
			JSONObject jsonObject = RequestUtil.getJsonObject(request);
			EventBattleLogJson eblj =JSONObject.toJavaObject(jsonObject, EventBattleLogJson.class);
			EventBattleLogResultJson eblrj =new EventBattleLogResultJson();
			if(eblj !=null)
			{
				PlayerInfo pi =Cache.getInstance().getPlayerInfo(eblj.playerId, request.getSession());
				if(pi !=null)
				{
					int bNum =eblj.bNum;
					if(pi.bNum<bNum && pi.ebrj.bNum==bNum)//第一次请求
					{
//						long time=System.currentTimeMillis();
						boolean isRight=true;
						//概率校验
						int roll=Random.getNumber(100);
						if(roll<checkPro)
						{
							//TODO校验
						}
						boolean p=true;
						if(isRight)
						{
							if(p)
							{
								//记录每日任务进度
								ActivityController.updateTaskComplete(7, pi, 1);
								pi.player.addActive(7,1);
								FBeventData fbData =FBeventData.getFBeventData(pi.ebrj.id);
								/**如果胜利**/
								if(eblj.r==1)
								{
									//扣除体力
									pi.player.removePower(fbData.cost);
									//战前玩家信息
									eblrj.lv0=pi.player.getLevel();
									eblrj.ce0 =pi.player.getCurExp();
									eblrj.power0 =pi.player.getPower();
									PlayerData pd=PlayerData.getData(pi.player.getLevel()+1);
									if(pd!=null)	
									{
										eblrj.me0=pd.exp;
									}
									//玩家获得经验
									pi.player.addExp(fbData.personexp);
									//玩家获得金币
									pi.player.addGold((int)Cache.getGoldDropMul()*fbData.coins);
									//如果是死亡洞穴则加金罡心
									int get = 0;
									if (eblj.t == 1)
									{
										get = BloodValueData.getGet(eblj.bv);
										pi.player.addDiamond(get);
									}
									eblrj.ad = get;
									//战后玩家信息
									eblrj.lv1=pi.player.getLevel();
									eblrj.ce1=pi.player.getCurExp();
									eblrj.power1 =pi.player.getPower();
									pd=PlayerData.getData(pi.player.getLevel()+1);
									if(pd!=null)
									{
										eblrj.me1=pd.exp;
									}
									//战前/战后角色卡信息,格式:cardId-level-curExp-maxExp-hp-atk-def
									List<String> cards0=new ArrayList<String>();
									List<String> cards1=new ArrayList<String>();
									for(Card c:pi.getCardGroup().cards)
									{
										if(c!=null)
										{
											CardData cd=CardData.getData(c.getCardId());
											//战前
											int maxExp=0;
											CardExpData ced=CardExpData.getData(c.getLevel()+1);
											if(cd!=null && ced!=null)
											{
												maxExp=ced.starexps[cd.star-1];
											}
											int maxHp=(int)Statics.getCardSelfMaxHp(c.getCardId(), c.getLevel(), c.getBreakNum());
											int atk=(int)Statics.getCardSelfMaxAtk(cd.id, c.getLevel(), c.getBreakNum());
											int def=(int)Statics.getCardSelfMaxDef(cd.id, c.getLevel(), c.getBreakNum());
											cards0.add(c.getCardId()+"-"+c.getLevel()+"-"+c.getCurExp()+"-"+maxExp+"-"+maxHp+"-"+atk+"-"+def);
											//角色卡获得经验
											c.addExp(fbData.cardexp);
											//战后
											ced=CardExpData.getData(c.getLevel()+1);
											if(cd!=null && ced!=null)
											{
												maxExp=ced.starexps[cd.star-1];
											}
											maxHp=(int)Statics.getCardSelfMaxHp(c.getCardId(), c.getLevel(), c.getBreakNum());
											atk=(int)Statics.getCardSelfMaxAtk(cd.id, c.getLevel(), c.getBreakNum());
											def=(int)Statics.getCardSelfMaxDef(cd.id, c.getLevel(), c.getBreakNum());
											cards1.add(c.getCardId()+"-"+c.getLevel()+"-"+c.getCurExp()+"-"+maxExp+"-"+maxHp+"-"+atk+"-"+def);
										}
									}
									eblrj.cs0=cards0;
									eblrj.cs1=cards1;
									eblrj.ag=fbData.coins;
									//玩家获得物品奖励
									eblrj.ds=new ArrayList<String>();
									List<Integer> cardIds =new ArrayList<Integer>();
									if(pi.ebrj.s!=null)
									{
										for(String drop:pi.ebrj.s)
										{
											if(drop==null || "".equals(drop))
											{
												continue;
											}
											eblrj.ds.add(drop);
											String[] ss=drop.split("-");
											int type=StringUtil.getInt(ss[0]);
											switch (type)
											{
											case 1://item
												String[] temp=ss[1].split(",");
												pi.addItem(StringUtil.getInt(temp[0]), StringUtil.getInt(temp[1]));
												break;
											case 2://equip
												pi.addEquip(StringUtil.getInt(ss[1]));
												break;
											case 3://card
												temp=ss[1].split(",");
												cardIds.add(StringUtil.getInt(temp[0]));
												pi.addCard(StringUtil.getInt(temp[0]), StringUtil.getInt(temp[1]));
												break;
											case 4://skill
												pi.addSkill(StringUtil.getInt(ss[1]),1);
												break;
											case 5://passiveSkill
												pi.addPassiveSkill(StringUtil.getInt(ss[1]));
												break;
											}
										}
									}
									if(cardIds.size()>0)
									{
										pi.getNewUnitSkill(cardIds);
									}
									int id=pi.ebrj.id;
									//改变关卡进入次数
									String fbNum="";
									if(fbData.timestyle==1)
									{
										fbNum =pi.player.getFBnum1();
									}
									else if(fbData.timestyle==2)
									{
										fbNum =pi.player.getFBnum2();
									}
									
									if(fbNum !=null)
									{
										String [] str =fbNum.split(",");
										boolean a=true;
										for(int k=0;k<str.length;k++)
										{
											if(str[k] !=null && str[k].length()>0)
											{
												String [] temp =str[k].split("-");
												if(StringUtil.getInt(temp[0])==id)
												{
													str[k] =temp[0]+"-"+(StringUtil.getInt(temp[1])+1);
													a=false;
													break;
												}
											}
										}
										if(a)
										{
											if(fbData.timestyle==1)
											{
												pi.player.setFBnum1(pi.player.getFBnum1()+","+id+"-"+1);
											}
											else if(fbData.timestyle==2)
											{
												pi.player.setFBnum2(pi.player.getFBnum2()+","+id+"-"+1);
											}
										}
										else
										{
											String s="";
											for(int k=0;k<str.length;k++)
											{
												if(str[k]!=null && str[k].length()>0)
												{
													if(s ==null || s.length()==0)
													{
														s =str[k];
													}
													else
													{
														s =s +","+str[k];
													}
												}
											}
											if(fbData.timestyle==1)
											{
												pi.player.setFBnum1(s);
											}
											else
											{
												pi.player.setFBnum2(s);
											}
										}
									}
									else
									{
										if(fbData.timestyle==1)
										{
											pi.player.setFBnum1(id+"-"+1);
										}
										else if(fbData.timestyle==2)
										{
											pi.player.setFBnum2(id+"-"+1);
										}
									}
									//开始冷却时间
									if(pi.ebrj !=null)
									{
										EventData eData =EventData.getEventData(pi.ebrj.eid);
										if(eData !=null)
										{
											if(eData.positionid ==1)
											{
												pi.eventcdtime1 =System.currentTimeMillis();
											}
											else if(eData.positionid ==2)
											{
												pi.eventcdtime2 =System.currentTimeMillis();
											}
											else if(eData.positionid ==3)
											{
												pi.eventcdtime3 =System.currentTimeMillis();
											}
										}
									}
								}
								else
								{
									//战斗失败
									//角色卡,格式:cardId-level-curExp-maxExp-hp-atk-def
									List<String> cards0=new ArrayList<String>();
									for(Card c:pi.getCardGroup().cards)
									{
										if(c!=null)
										{
											CardData cd=CardData.getData(c.getCardId());
											//战前
											int maxExp=0;
											CardExpData ced=CardExpData.getData(c.getLevel()+1);
											if(cd!=null && ced!=null)
											{
												maxExp=ced.starexps[cd.star-1];
											}
											int maxHp=(int)Statics.getCardSelfMaxHp(c.getCardId(), c.getLevel(), c.getBreakNum());
											int atk=(int)Statics.getCardSelfMaxAtk(cd.id, c.getLevel(), c.getBreakNum());
											int def=(int)Statics.getCardSelfMaxDef(cd.id, c.getLevel(), c.getBreakNum());
											cards0.add(c.getCardId()+"-"+c.getLevel()+"-"+c.getCurExp()+"-"+maxExp+"-"+maxHp+"-"+atk+"-"+def);
										}
									}
									eblrj.cs0=cards0;
								}
								eblrj.id =pi.erj.id;
								eblrj.r =eblj.r;
							}
							playlogger.info("玩家"+pi.player.getId()+"副本战斗结束");
						}
						else
						{
							//校验出错,写入日志
							eblrj.errorCode=2;
							battleCheckLogger.error("校验出错:"+JSON.toJSONString(eblrj));
						}
					}
					else
					{
						eblrj =pi.eblrj;
					}
				}
				else
				{
					eblrj.errorCode =-3;
				}
			}
			else
			{
				eblrj.errorCode=-1;
			}
			
			//获取参数
			Cache.recordRequestNum(eblrj);
			String msg = JSON.toJSONString(eblrj);
			logger.info("msg:"+msg);
			RequestUtil.setResponseMsg(request, msg);
			return new ModelAndView("/user/result.vm");
		}
		catch (Exception e) 
		{
			errorlogger.error(this.getClass().getName()+"->"+Thread.currentThread().getStackTrace()[1].getMethodName()+"():",e);
			RequestUtil.removeKey(request);
			String newKey = RequestUtil.setNewKey(request);
			RequestUtil.setResult(request, newKey);
		}
		return new ModelAndView("/user/result.vm");
	}
}
